﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using CookComputing.MetaWeblog;
using CookComputing.XmlRpc;
using System.Configuration;
using System.IO;
using mBlog.Services;

namespace mBlog.Core
{
    public class MetaWeblog : XmlRpcService, IMetaWeblog
    {
        private IPostService postService;
        private ICategoryService categoryService;

        public MetaWeblog(IPostService pService, ICategoryService cService)
        {
            this.postService = pService;
            this.categoryService = cService;
        }
        public UserBlog[] getUsersBlogs(string appKey, string username, string password)
        {
            return new UserBlog[] { new UserBlog { blogid = "fengqijun", blogName = "Jun1st's Notes", url = "http://fengqijun.com" } };
        }

        public object editPost(string postid, string username, string password, CookComputing.MetaWeblog.Post post, bool publish)
        {
            if (Validate(username, password))
            {
                mBlog.Models.Post oldPost = postService.Single(long.Parse(postid));
                if (oldPost.ID > 0)
                {
                    return "Post doesn't exists";
                }
                else
                {
                    oldPost.Title = post.title;
                    oldPost.Content = post.description;

                    postService.Update(oldPost);

                    return "Post updated";
                }
            }
            else
            {
                return "Invalid user";
            }
        }

        public CategoryInfo[] getCategories(string blogid, string username, string password)
        {
            if (Validate(username, password))
            {
                int count = categoryService.Count();
                IList<Models.Category> cats = categoryService.Get();
                CategoryInfo[] categories = new CategoryInfo[count];
                for (int i = 0; i < count; i++)
                {
                    categories[i] = new CategoryInfo()
                    {
                        categoryid = cats[i].ID.ToString(),
                        description = cats[i].Name,
                        title = cats[i].UrlName,
                        rssUrl = cats[i].UrlName,
                        htmlUrl = cats[i].UrlName
                    };
                }

                return categories;
            }
            else
            {
                return null;
            }
        }

        public CookComputing.MetaWeblog.Post getPost(string postid, string username, string password)
        {
            if (Validate(username, password))
            {
                Models.Post post = postService.Single(long.Parse(postid));

                return new CookComputing.MetaWeblog.Post()
                   {
                       postid = post.ID,
                       description = post.Content
                   };

            }
            else
            {
                return new Post();
            }
        }

        public Post[] getRecentPosts(string blogid, string username, string password, int numberOfPosts)
        {
            if (Validate(username, password))
            {
                List<Models.Post> posts = postService.Get(0, numberOfPosts).ToList();
                List<Post> recentPosts = new List<Post>();

                posts.ForEach(post => recentPosts.Add(
                    new Post()
                        {
                            title = post.Title,
                            description = post.Content,
                            mt_excerpt = post.Content,
                            dateCreated = post.PostedTime,
                            categories = (from c in post.Categories
                                          select c.Name).ToArray()
                        }
                                          ));

                return recentPosts.ToArray();

            }
            else
            {
                return null;
            }
        }

        public string newPost(string blogid, string username, string password, Post post, bool publish)
        {
            if (Validate(username, password))
            {
                Models.Post newPost = new Models.Post
                                          {
                                              Title = post.title,
                                              Content = post.description,
                                              Excerpt = post.mt_excerpt,
                                              PostedTime = DateTime.Now,
                                              IsPublished = publish
                                          };
                if (publish)
                {
                    newPost.PublishedTime = DateTime.Now;
                }
                else
                {
                    newPost.PublishedTime = null;
                }

                newPost.Categories = new List<Models.Category>();

                foreach (string cat in post.categories)
                {
                    Models.Category category = categoryService.Single(cat);
                    if (category != null && category.ID > 0)
                    {
                        newPost.Categories.Add(category);
                    }
                }

                postService.Add(newPost);

                return newPost.ID.ToString();
            }
            return string.Empty;
        }

        public UrlData newMediaObject(string blogid, string username, string password, FileData file)
        {
            if (!Validate(username, password))
            {
                throw new XmlRpcFaultException(0, "Login failed");
            }

            string uploadPhysicalPath = Context.Server.MapPath(ConfigurationManager.AppSettings["uploadsPath"]);
            string uploadWebPath = VirtualPathUtility.ToAbsolute(ConfigurationManager.AppSettings["uploadsPath"]);

            uploadPhysicalPath = Path.Combine(uploadPhysicalPath, file.name);

            if (!Directory.Exists(Path.GetDirectoryName(uploadPhysicalPath)))
            {
                Directory.CreateDirectory(Path.GetDirectoryName(uploadPhysicalPath));
            }

            File.WriteAllBytes(uploadPhysicalPath, file.bits);

            return new UrlData()
            {
                url = Path.Combine(uploadWebPath, file.name)
            };
        }

        private bool Validate(string userName, string password)
        {
            if (userName == "jun1st" && password == ConfigurationManager.AppSettings["Password"])
            {
                return true;
            }
            else
            {
                return false;
            }
        }
    }
}
